home *** CD-ROM | disk | FTP | other *** search
/ Collection of Tools & Utilities / Collection of Tools and Utilities.iso / c / cug190.zip / AS68.C next >
Text File  |  1985-11-15  |  24KB  |  891 lines

  1. /******************************************************************
  2.     as68.c, the source of a 68000 assembler....
  3. */
  4.  
  5. /*        (C) Copyright 1982 Steve Passe        */
  6. /*        All Rights Reserved                    */
  7.  
  8. /*  ver. 1.00 */
  9. /* created 10/7/82 */
  10.  
  11. /* version 1.01
  12.  
  13.     8/30/83    ver. 1.01 modified for Aztec ver. 1.05g    smp
  14.     12/23/83    fixed 24 bit address bug in flush_rcrd smp
  15.     12/24/83    fixed lowercase a-f in S-records smp
  16.  
  17. */
  18.  
  19. /* begincode */
  20.  
  21. /* includes */
  22.  
  23. #define AZTECZII 1
  24.  
  25. #ifndef AZTECZII
  26. #include <stdio.h>
  27. #else
  28. #include "stdio.h"                                /* with aztecII compiler */
  29. #endif
  30. #include "b:as68.h"
  31.  
  32. /* externals */
  33.  
  34. struct _symbol *symtbl;
  35. struct _symbol *syms_head;                    /* head of sym table free space */
  36. char *syms_tail;                            /* tail of sym table free space */
  37. int symspace = SYMTSIZE;                    /* bytes in symbol table */
  38. int symbols = 0;                            /* number of symbols in table */
  39.  
  40. FLAG fatal = NO;
  41. char pass = 1;                                /* present pass number, 1 or 2 */
  42. unsigned line_count = 0;                    /* line number of source file */
  43. unsigned list_count = 0;                    /* line # of list file */
  44. long loc_counter = 0;                        /* address to assemble obj code */
  45. int loc_plus = 0;                            /* increment to loc counter */
  46. char lcksm;                        /* bytes + addr. + count + lcksm == 0xff */
  47. FLAG abs_long = YES;                        /* default to absolute long add.*/
  48. FLAG rorg = NO;                                /* prog. counter relative flag */
  49. FLAG do_label = YES;                        /* process label if set */
  50. char statement[STMNT_SIZE];                    /* statement line buffer */
  51. char label[32];                                /* bufr for label from preparse */
  52. char instr[32];                                /* bufr for mnem, psdo or macro */
  53. char *opfld_ptr;                            /* pointer to operand field */
  54. char *stmnt_ptr;                            /* ptr to statement field */
  55. char stmnt_typ;                                /* statement type, instr, pseudo */
  56. int wrap = 80;                                /* wrap column for list output */
  57. FLAG trunc = NO;                            /* truncate lines in listing */
  58. char source_name[FNAME_SIZE];                /* source file name */
  59. int src_level = 0;                            /* source file level */
  60. FILE *_src[SRCLEVELS];                        /* source file descripters */
  61. FLAG objchnl = 's';                            /* Motorola S ('s') or nil ('x') */
  62. FLAG obj_open = NO;                            /* object channel open flag */
  63. char of_disk = NULL;                        /* default object file drive */
  64. char object_name[FNAME_SIZE];                /* object file name */
  65. FILE *obj_f;                                /* object file descripter */
  66. FLAG lstchnl = NO;                            /* list channel(s) open */
  67. FLAG nolist = NO;                            /* flag for list/nolist pseudos */
  68. FLAG lcon = NO;                                /* list to console flag */
  69. FLAG llst = NO;                                /* list to list device flag */
  70. FLAG lfile = NO;                            /* list to file flag */
  71. FLAG lfile_open = NO;                        /* list file open flag */
  72. char lf_disk = NULL;                        /* default list file drive */
  73. char list_name[FNAME_SIZE];                    /* listing file name */
  74. FILE *lst_f, *lst_d;                        /* listing file & dev descripter */
  75. FLAG errchnl = YES;                            /* error channel(s) open */
  76. FLAG econ = YES;                            /* errors to console flag */
  77. FLAG elst = NO;                                /* errors to list device flag */
  78. FLAG elfile = NO;                            /* errors to listing file */
  79. FLAG efile = NO;                            /* errors to error file */
  80. FLAG efile_open = NO;                        /* error file open flag */
  81. char ef_disk = NULL;                        /* default error file drive */
  82. char error_name[FNAME_SIZE];                /* error file name */
  83. FILE *err_f;                                /* error file descripter */
  84.  
  85. struct _oprnd op1, op2;                    /* structs to hold operand val */
  86.  
  87. char code[12];                    /* 12 minimum for overflow */
  88. char buf[85];
  89.  
  90. long lex_val;
  91. char *p;
  92.  
  93. extern struct _mtable mtable[];
  94.  
  95. /* beginmain */
  96.  
  97. main(argc, argv)
  98. int argc;
  99. char *argv[];
  100. {
  101.  
  102.     register int x, y;
  103.     char *c_ptr;                    /* scratch pointer to char */
  104.     char _ext[5];                    /* scratch ext buffer */
  105.     struct _ptable *pt;                /* function ptr returned by psdosearch */
  106.     struct _mtable *mt;                /* function ptr returned by mnemsearch */
  107.     long _dtol();
  108.  
  109.     puts("\nas68, ver 1.01, 68000 assembler, (C) Copyright 1982 Steve Passe\n");
  110.  
  111. /** parse the command line, setting variables as needed */
  112.  
  113.     if (argc < 2) {
  114.         puts("\n...source file?");
  115.         exit(0);
  116.     }
  117. /** set flag variables according to command line args */
  118.  
  119.     for (x = 2; x < argc; ++x) {
  120.         switch (tolower(argv[x][0])) {
  121.         case 'e':                                        /* error file opt */
  122.             econ = NO;
  123.             for (y = 1; argv[x][y]; ++y) {
  124.                 switch (tolower(argv[x][y])) {
  125.                 case 'c':    econ = YES;        continue;
  126.                 case 'l':    elst = YES;        continue;
  127.                 case 'f':    elfile = YES;    continue;
  128.                 case 'e':    efile = YES;
  129.                     if (argv[x][y+1] && argv[x][y+2] == ':') {
  130.                         ef_disk = argv[x][++y];
  131.                         ++y;
  132.                     }
  133.                     continue;
  134.                 default:    errchnl = NO;
  135.                 }
  136.             }
  137.             continue;
  138.         case 'l':                                        /* list file opt */
  139.             lstchnl = YES;
  140.             for (y = 1; argv[x][y]; ++y) {
  141.                 switch (tolower(argv[x][y])) {
  142.                 case 'c':    lcon = YES;        continue;
  143.                 case 'l':    llst = YES;        continue;
  144.                 case 'f':    lfile = YES;
  145.                     if (argv[x][y+1] && argv[x][y+2] == ':') {
  146.                         lf_disk = argv[x][++y];
  147.                         ++y;
  148.                     }
  149.                     continue;
  150.                 default:    lstchnl = NO;
  151.                 }
  152.             }
  153.             continue;
  154.         case 'o':                                        /* object file opt */
  155.             for (y = 1; argv[x][y]; ++y) {
  156.                 switch (tolower(argv[x][y])) {
  157.                 case 's':    objchnl = 's';
  158.                     if (argv[x][y+1] && argv[x][y+2] == ':') {
  159.                         of_disk = argv[x][++y];
  160.                         ++y;
  161.                     }
  162.                     continue;
  163.                 default:    objchnl = 'x';
  164.                 }
  165.             }
  166.             continue;
  167.         case 's':
  168.             opfld_ptr = &argv[x][1];
  169.             symspace = (int) _dtol();
  170.             continue;
  171.         case 'w':
  172.             wrap = atoi(&argv[x][1]);
  173.             if (wrap < 60) wrap = 60;
  174.             continue;
  175.         case 't':
  176.             trunc = YES;
  177.             continue;
  178.         default:    puts("\nhuh?");    exit(0);
  179.         }
  180.     }
  181.  
  182.     if (!(symtbl = alloc(symspace))) {    /* allocate space for symbol table */
  183.         printf("\n...symbol table too large (%d)", symspace);
  184.         exit(0);
  185.     }
  186.     syms_head = symtbl + 1;                            /* init free space head */
  187.     syms_tail = symtbl;    syms_tail += symspace;        /* init free space tail */
  188.  
  189.     symtbl[0]._sym = "";                            /* dummy entry */
  190.     symtbl[0]._val = NULL;
  191.     symtbl[0]._atr = NULL;
  192.  
  193. /* initialize sourcename, errname, listname, and objname */
  194.  
  195.     if (too_long(argv[1], 14)) {
  196.         exit(0);
  197.     }
  198.     if (argv[1][1] == ':') {                    /* a disk identifier exists */
  199.         strcpy(source_name, argv[1]);                /* get source file name */
  200.     }
  201.     else {                                        /* default to logged in disk */
  202.         if (too_long(argv[1], 12)) {
  203.             exit(0);
  204.         }
  205.         source_name[0] = bdos(CURR_DISK, 0) + 'A';        /* read default disk */
  206.         source_name[1] = ':';                            /* separator */
  207.         source_name[2] = '\0';                            /* make a string */
  208.         strcat(source_name, argv[1]);                    /* add the name */
  209.     }
  210.     if (c_ptr = cisat('.', source_name)) {        /* if extension */
  211.         word_copy(_ext, 4, c_ptr);                    /* save ext */
  212.         *c_ptr = '\0';                                /* erase it */
  213.     }
  214.     else strcpy(_ext, ".sa");                    /* default extension */
  215.     if (too_long(source_name, 10)) {
  216.         exit(0);
  217.     }
  218.     strcpy(object_name, source_name);            /* make object file name */
  219.     switch (objchnl) {
  220.     case 'x':    break;                                /* none wanted */
  221.     case 's':    strcat(object_name, ".mx");        /* for Motorola S FILE */
  222.                 break;
  223.     default:    printf("\n...bad object file type ('%c')", objchnl);
  224.     }
  225.     if (of_disk) object_name[0] = of_disk;        /* pick up option */
  226.     strcpy(list_name, source_name);
  227.     strcat(list_name, ".ls");                    /* make list file name */
  228.     if (lf_disk) list_name[0] = lf_disk;        /* option */
  229.     strcpy(error_name, source_name);
  230.     strcat(error_name, ".err");                    /* make error file name */
  231.     if (ef_disk) error_name[0] = ef_disk;        /* option */
  232.     strcat(source_name, _ext);                    /* add ext. */
  233.  
  234.     /* open appropriate source, list, error, and object files */
  235.  
  236.     if (!(_src[0] = fopen(source_name, "r"))) {
  237.         printf("\n...can't open source (\"%s\")", source_name);
  238.         exit(0);
  239.     }
  240.                                     /* open list, err, and obj as needed */
  241.     if (objchnl != 'x') {
  242.         if (!(obj_f = fopen(object_name, "w"))) {
  243.             printf("\n...can't open object (\"%s\")", object_name);
  244.             exit(0);
  245.         }
  246.         obj_open = TRUE;
  247.         obj_out(OPEN, 0, 0);
  248.     }
  249.     if (lfile) {
  250.         if (!(lst_f = fopen(list_name, "w"))) {
  251.             printf("\n...can't open list (\"%s\")", list_name);
  252.             exit(0);
  253.         }
  254.         lfile_open = TRUE;
  255.     }
  256.     if (efile) {
  257.         if (!(err_f = fopen(error_name, "w"))) {
  258.             prin